package cn.stalk.compare.field;

import cn.stalk.compare.DataAccessor;
import cn.stalk.compare.anno.AComparable;

import java.lang.reflect.Field;

public class FieldDataAccessor<T> extends DataAccessor<T, Object> {

    private final static Number ZERO = 0;

    private Field field;
    private boolean nullToZero;
    private boolean isNumber;

    public FieldDataAccessor(Field field) {
        this(field, true, false, false, null, false);
    }

    public FieldDataAccessor(Field field, AComparable comparable) {
        this(field, comparable.blankToNull(), comparable.trim(), comparable.nullToZero(), comparable.splitToList(), comparable.toSet());
    }

    public FieldDataAccessor(Field field, boolean blankToNull, boolean trim, boolean nullToZero, String arraySeparator, boolean arrayUnique) {
        super(field.getName(), blankToNull, trim, arraySeparator, arrayUnique);
        this.nullToZero = nullToZero;
        this.field = field;
        this.field.setAccessible(true);
        isNumber = Number.class.isAssignableFrom(field.getType()) || field.getType().isPrimitive();
    }

    public void setNullToZero(boolean nullToZero) {
        this.nullToZero = nullToZero;
    }

    public boolean isNullToZero() {
        return nullToZero;
    }

    @Override
    public Object apply(T t) {
        try {
            Object value = field.get(t);
            if (nullToZero && isNumber && null == value) {
                return ZERO;
            }
            return value;
        } catch (Exception e) {
            return null;
        }
    }

}
